package com.smile.frame.websocket.netty.service.repository;

import io.netty.channel.Channel;
import lombok.extern.slf4j.Slf4j;

import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;

/**
 * channelId与client map
 *
 * @author LGC
 */
@Slf4j
public class ClientRepository {

    /**
     * 存储channel的id和用户主键的映射，客户端保证用户主键传入的是唯一值，解决问题四，如果是集群中需要换成redis的hash数据类型存储即可
     * 问题四:由于客户端和websocket服务器集群中的某个节点建立长连接是随机的，如何解决服务端向某个或某些部分客户端推送消息？
     */
    public final static Map<String, String> CLIENT_MAP = new ConcurrentHashMap<>();

    /**
     * 通过通道ID获取client
     */
    public static String getClient(String channelId) {
        return CLIENT_MAP.get(channelId);
    }

    /**
     * 通过通道ID获取通道
     */
    public static String getClient(Channel channel) {
        return CLIENT_MAP.get(channel.id().asLongText());
    }

    /**
     * 是否存在client
     */
    public static Boolean containsKey(String channelId) {
        return CLIENT_MAP.containsKey(channelId);
    }

    /**
     * 保存client
     */
    public static void putClient(String channelId, String client) {
        CLIENT_MAP.put(channelId, client);
        log.info("channelId:{},client:{}", channelId, client);
    }

    /**
     * 保存client
     */
    public static void putClient(Channel channel, String client) {
        CLIENT_MAP.put(channel.id().asLongText(), client);
    }


    /**
     * 移除管道
     *
     * @param channelId
     */
    public static void removeClient(String channelId) {
        CLIENT_MAP.remove(channelId);
    }

    /**
     * 移除管道
     *
     * @param channel
     */
    public static void removeClient(Channel channel) {
        CLIENT_MAP.remove(channel.id().asLongText());
    }


}
